# 4 - Laravel 5.2 Database

參考:Larvel 5 實務專題範例教學

Table : student

欄位名稱 型態 屬性 空值 預設值 額外資訊 描述
id int UNSIGNED AUTO_INCREMENT 編號
user_id int UNSIGNED
no varchar 唯一鍵 學號
tel varchar 電話
created_at timestamp NULL 建立時間
updated_at timestamp NULL 更新時間

Table : score

欄位名稱 型態 屬性 空值 預設值 額外資訊 描述
id int UNSIGNED AUTO_INCREMENT 編號
student_id int UNSIGNED 學生編號
chinese int UNSIGNED 中文
english int UNSIGNED 英文
math int UNSIGNED 數學
total int UNSIGNED 總分
created_at timestamp NULL 建立時間
updated_at timestamp NULL 更新時間

UNSIGNED -> 不要負數


# 產生migration檔案

migration是用來生成table的檔案

php56 artisan make:migration create_student_table --create=student
php56 artisan make:migration create_score_table --create=score

if [ErrorException] ... failed to open stream: No such file or directory run composer dump-autoload 參考 (opens new window)


app/database/migrations/2017_10_21_071807_create_student_table.php

public function up(){
    Schema::create('student', function (Blueprint $table) {
        $table->increments('id');//遞增的ID(主鍵)
        //$table->unsignedInteger('user_id');
        $table->integer('user_id')->unsigned();
        $table->string('no')->uniqid();
        $table->string('tel');
        $table->timestamps();
    });
}

app/database/migrations/2017_10_21_071807_create_student_table.php

public function up(){
    Schema::create('score', function (Blueprint $table) {
        $table->increments('id');
        $table->integer('student_id')->unsigned();
        $table->integer('chinese')->unsigned();
        $table->integer('english')->unsigned();
        $table->integer('math')->unsigned();
        $table->integer('total')->unsigned();
        $table->timestamps();
    });
}

up() php56 artisan migrate down() php56 artisan migrate:rollback

更新 php56 artisan migrate:refresh 會del晒全部資料!!!score

-w500

如果遇到file被無視的情況 暫時移除預設個兩個file[2014_xxx.php] 之後就可以用到 如上圖 原因未明...

Class 'xxx' not found
composer dump-autoload


如果之後想加多項columns (ALTER TABLE)

php artisan make:migration add_backgroundImage__to_rooms_table --table=rooms

php artisan make:migration add_votes_to_users_table --table=users

public function up()
{
    Schema::table('tableName', function (Blueprint $table) {
        $table->string('new column');
    });
}

# Eloquent model

Eloquent是用來對database進行操作

php artisan make:model Score    //app/Score.php
php artisan make:model Student  //app/Student.php

app/Score.php

...
use \App\Student as StudentEloquent;

class Score extends Model
{
    protected $table = 'score';

    public function student(){
    	return $this->belongsTo(StudentEloquent::class); 
        //預設外鍵(fk) 'tableName'_id => score.student_id

        //效果 => table:score.student_id(fk) 搵 -> table:student.id(pk)
        //https://laravel.tw/docs/5.1/eloquent-relationships
    }

    //call function個陣 xxxxxx() -> Laravel會detect function name -> scope-xxxxx 
    public function scopeOrderByTotal($query){
    	return $query->orderBy('score.total','DESC');
    }

    public function scopeOrderBySubject($query){
    	return $query->orderBy('score.chinese','DESC')->orderBy('score.english','DESC')->orderBy('score.math','DESC');
    }
}

app/Student.php

...
use \App\Score as ScoreEloquent;
use \App\User as UserEloquent;

class Student extends Model
{
    protected $table = 'student';

    public function user(){
        return $this->belongsTo(UserEloquent::class); 
        //student.user_id <=> user.id
    }

    public function score(){
        return $this->hasOne(ScoreEloquent::class);
        //student.id <=> score.student_id
    }
}scopeOrderByTotal

app/User.php

...
    public function student(){
        return $this->hasOne(StudentEloquent::class);
        //user.id <=> student.user_id
    }

# Eloquent 資料撈取

app/Http/Controller/BoardController

class BoardController extends Controller
{

	public function getIndex(){
		return View::make('board',['scores'=>ScoreEloquent::with('student')->orderByTotal()->orderBySubject()->get()]);
		//效果 拎學生成績同資料 -> 排序 (總分 -> 中文 -> 英文 -> 數學)
		
		//1. student():score
		//2. orderByTotal() -> scopeOrderByTotal()
		//3. orderBySubject() -> scopeOrderBySubject()
		//scope https://9iphp.com/web/laravel/5-laravel-eloquent-tips-tricks.html


	}
	//ScoreEloquent::with('student')
	//Score.phpx -> student()

    public function getName(){
    	return Route::currentRouteAction();
    	//display : App\Http\Controllers\BoardController@getName
    }


}

app/Http/Controller/StudentController


use \App\Student as StudentEloquent;

    public function getStudentData($student_no){
        $student = StudentEloquent::where('no', $student_no)->firstOrFail();
        //student.no = $student_no ? get first data : error
        return View::make('student', [
            'student' => $student,
            'user'    => $student->user, //call Student:user()
            'score'   => $student->score, //call Student:score()
            'subject' => null,
        ]);

    }

    public function getStudentScore($student_no, $subject = null){
        $student = Student::where('no', $student_no)->firstOrFail();
        return View::make('student', [
            'student' => $student,
            'user'    => $student->user,
            'score'   => $student->score,
            'subject' => $subject,
        ]);
    }

# Factory

生成大量虛擬資料

本身已預設有database/factories/ModelFactory.php

負責設定生成的規則

$factory->define(App\User::class, function (Faker\Generator $faker) {
    return [
        'name' => $faker->name,
        'email' => $faker->safeEmail,
        'password' => bcrypt(str_random(10)),
        'remember_token' => str_random(10),
    ];
});

$factory->define(App\Student::class,function(Faker\Generator $faker){
	return [
		'user_id' => function(){
			return factory(App\User::class)->create()->id;
		},
		'no' => $faker->regexify('s[0-9]{10}'),
		'tel' => $faker->phoneNumber()
	];
});

$factory->define(App\Score::class,function(Faker\Generator $faker){
	return [
		'student_id' => function(){
			return factory(App\Student::class)->create()->id;
		},
		'chinese' => $faker->numberBetween(0,100),
		'english' => $faker->numberBetween(0,100),
		'math' => $faker->numberBetween(0,100)
	];
});

Seeder負責執行factory 生成 : php artisan make:seeder TestTableSeeder

database/seeds/TestTableSeeder.php

...
use App\Score as Score;

class TestTableSeeder extends Seeder
{
    /**
     * Run the database seeds.
     *
     * @return void
     */
    public function run(){
        //生成20個
        $scores = factory(Score::class,20)->create()->each(function($score){
        	$score->total=$score->chinese+$score->english+$score->math;
        	//total = chinese + english + math
        	$score->save();
        });
    }
}

系統預設有database/seeds/DatabaseSeeder.php,因此為了方便 會集中在識檔案call

...
class DatabaseSeeder extends Seeder
{
    public function run()
    {
        $this->call(TestTableSeeder::class);
    }
}

執行php artisan db:seed

Last Updated: Sun Aug 11 2019 13:25:40 GMT+0000
贊助商連結
(adsbygoogle = window.adsbygoogle || []).push({});